package com.yyfax.pay.common.util;

import java.util.Iterator;
import java.util.Set;

import javax.annotation.Resource;
import javax.validation.ConstraintViolation;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.stereotype.Component;

import com.yyfax.commons.json.JacksonUtil;
import com.yyfax.framework.aspect.DefaultValidator;
import com.yyfax.framework.common.Log;
import com.yyfax.framework.common.Pair;
import com.yyfax.pay.common.model.to.YYPayFormReq;
import com.yyfax.pay.common.model.vo.ValidResult;

/**
 * hibernate参数绑定校验工具类
 * 
 * @author buyi
 * @date 2017-09-18 17:04:36
 * @since v2.0.0
 */
@Component
public class ValidationUtil {
	private static final Logger logger = LoggerFactory.getLogger(ValidationUtil.class);

	@Resource
	private DefaultValidator validator;

	/**
	 * 支付form表单参数校验
	 * 
	 * @author buyi
	 * @date 2017-09-18 19:44:56
	 * @since v2.0.0
	 * @param req
	 * @param clazz
	 * @return
	 */
	public <T> Pair<ValidResult, T> validateForWeb(YYPayFormReq req, Class<T> clazz) {
		final String op = "ValidationUtil.validateForWeb";

		ValidResult validResult = validate(req);
		if (!validResult.isOk()) {
			// 如果验签不通过
			return Pair.of(validResult, null);
		}

		try {
			T t = JacksonUtil.fromJson(req.getParams(), clazz);
			if (t == null) {
				return Pair.of(ValidResult.newInstance(false, "param不能为空/格式非法"), null);
			}

			validResult = validate(t);

			return Pair.of(validResult, t);
		} catch (Exception e) {
			logger.error(Log.op(op).msg("反序列化参数出现异常").toString(), e);
			return Pair.of(ValidResult.newInstance(false, "param格式非法"), null);
		}
	}

	/**
	 * 进行实体参数绑定校验
	 * 
	 * @author buyi
	 * @date 2017-09-18 17:04:19
	 * @since v2.0.0
	 * @param obj
	 * @return
	 */
	private ValidResult validate(Object obj) {
		if (obj == null) {
			return ValidResult.newInstance(false, "参数不能为空");
		}

		Set<ConstraintViolation<Object>> violations = validator.getValidator().validate(obj);
		if (violations.isEmpty()) {
			// 如果验证信息为空，则表示参数绑定校验通过
			return ValidResult.newInstance(true, null);
		}

		return ValidResult.newInstance(false, getViolationMsg(violations));
	}

	/**
	 * 获取校验异常参数
	 * 
	 * @author buyi
	 * @date 2017-09-18 17:04:08
	 * @since v2.0.0
	 * @param violations
	 * @return
	 */
	private String getViolationMsg(Set<ConstraintViolation<Object>> violations) {
		StringBuilder sb = new StringBuilder();
		Iterator<ConstraintViolation<Object>> iter = violations.iterator();
		while (iter.hasNext()) {
			ConstraintViolation<Object> cv = iter.next();
			// String argsName = cv.getPropertyPath().toString();
			sb.append(cv.getMessage());
			if (iter.hasNext()) {
				sb.append(",");
			}
		}

		iter = null;
		return sb.toString();
	}
}
